#!/usr/bin/env python
# -*- coding: UTF-8 -*-

import fnmatch
import logging
import optparse
import re
import sys

from oriolus.docker.docker import DockerFactory, DockerError

# cli.py install c:\packets\agami-1.2.3.4.zip.ori
# cli.py remove agami-1.2.3.4
# cli.py list [pattern]

def exit(parser):
    parser.print_help()
    parser.destroy()
    sys.exit(0)

def check_args_count(args, number, parser):
    if len(args) != number:
        exit(parser)

def run():
    list = ("install", "remove", "list")

    usage = """usage: cli.py command [args]
    command:
        install (in) filename - install packet from specified file
        remove (rm) packet_name - remove packet by packet name
        list (ls) [keyword] - list packets in repository filtered by keyword"""

    parser = optparse.OptionParser(usage=usage, version = "OriolusDocker 0.3.0")
    parser.add_option("-l", dest = "loglevel", action="count", help = "set logging level, the count of option defines logging level (-l: DEBUG, -ll: INFO, -lll: WARNING, -llll: ERROR, -lllll: CRITICAL)")
    parser.add_option("--log", dest = "logfilename", default = "./docker.log.txt", help = "set log file name [default: %default]")
    parser.add_option("-r", "--regex", dest = "regex", action = "store_true", default = False, help = "Enable list filtration by regex [default: %default]")
    parser.add_option("-w", "--wildcard", dest = "wildcard", action = "store_true", default = False, help = "Enable list filtration by wildcard [default: %default]")
    parser.add_option("-c", "--config", dest = "config", help = "Path for docker configuration file")
    parser.add_option("-a", "--script_args", dest = "script_args", help = "Arguments to pass to packet scripts")
    parser.add_option("-b", "--base_path", dest = "base_path", help = "Base installation path")
    
    (options, args) = parser.parse_args()

    if len(args) == 0 or len(args) > 2:
        exit(parser)

    flag = False
    for each in args:
        if (not flag) and (each in list):
            flag = True
        elif (flag) and (each in list):
            exit(parser)

    if options.regex and options.wildcard:
        print "Options '--regex' and '--wildcard' can not be used at the same time!\n\n"
        exit(parser)
            
    loglevel = 0
    if options.loglevel:
        if options.loglevel > 5:
            options.loglevel = 5
        loglevel = options.loglevel * 10
        logging.basicConfig(level = loglevel, filename = options.logfilename, format = "%(asctime)-15s [%(thread)d] %(levelname)-5s %(name)s - %(message)s", )
    else:
        logging.basicConfig(level = logging.INFO, format = "[%(levelname)s] %(message)s", )

            
    factory = DockerFactory()
    if options.config:
        docker = factory.get_docker(options.config)
    else:
        docker = factory.get_docker()

    command = args[0]
    if command == "install" or command == "in":
        try:
            check_args_count(args, 2, parser)
            packet_path=args[1]
            docker.install(packet_path, options.base_path, options.script_args)
            print "Packet '%s' was installed succesfully." % packet_path
        except DockerError, message:
            print message
    elif command == "remove" or command == "rm":
        try:
            check_args_count(args, 2, parser)
            packet_name=args[1]
            docker.remove(packet_name=packet_name, args=options.script_args)
            print "Packet '%s' was removed succesfully." % packet_name
        except DockerError, message:
            print message
    elif command == "list" or command == "ls":
        packet_list = docker.search(get_all=True)
        
        if options.regex:
            check_args_count(args, 2, parser)
            
            try:
                regex = re.compile(args[1], re.IGNORECASE)
            except:
                print "Invalid regular expression."
                sys.exit(1)
                
            packet_list = [packet for packet in packet_list if regex.search(packet.name)]
        elif options.wildcard:
            check_args_count(args, 2, parser)
            packet_list = [packet for packet in packet_list if fnmatch.fnmatch(packet.name, args[1])]
        else:
            if len(args) != 1:
                check_args_count(args, 2, parser)
                packet_list = [packet for packet in packet_list if packet.name.find(args[1]) == 0]
                    
        if packet_list == []:
            print "Packets not found."
        else:
            for packet in packet_list:
                print "packet: %s, status: %s" % (packet.name, packet.get_status())
    else:
        parser.print_help()

if __name__ == "__main__":
    run()
